package com.lh.biz.impl;

import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.lh.biz.IOpenUserBiz;
import com.lh.biz.dto.in.openuser.BindUserInDto;
import com.lh.biz.dto.out.openuser.BindUserOutDto;
import com.lh.common.logic.LoginLogic;
import com.lh.dao.IOpenUserDao;
import com.lh.dao.IUserDao;
import com.lh.entity.OpenUser;
import com.lh.entity.User;
import com.lh.entity.OpenUser.OpenUserType;
import com.lh.exception.SystemException;
import com.lh.oauth.OAuth;
import com.lh.oauth.OAuthFactory;

/**
 * @author liuhui
 * @version 1.0
 * @date 2013-4-29 下午5:31:57
 */
@Service
@Transactional
public class OpenUserBizImpl implements IOpenUserBiz {

	@Resource
	private IOpenUserDao openUserDao;
	@Resource
	private IUserDao userDao;
	@Resource
	private LoginLogic  loginLogic;
	
	@Resource
	private OAuthFactory oAuthFactory;

	
	
	@Override
	public BindUserOutDto bindUser(BindUserInDto inDto) {
		BindUserOutDto out = new BindUserOutDto();
		OpenUserType openUserType = OpenUserType.get(inDto.getType());
		OAuth oa = oAuthFactory.getOAuth(openUserType);
		if(oa == null ){
			throw new SystemException("unknow open user type!~~");
		}
		OpenUser ou = oa.obtainOpenUser(inDto.getCode());
		if(ou ==null){//取消授权
			return out;
		}
		Map<String, Object> cond = new HashMap<String, Object>();
		cond.put("openid", ou.getOpenid());
		cond.put("type", ou.getType());
		List<OpenUser> ous  = openUserDao.list(cond);
		
		if(ous.size() == 0  ){
			User u = createUser(ou.getNickname());
			ou.setUser(u);
			openUserDao.insert(ou);
			oa.shareInfo(ou);
		}else {
			OpenUser openUser  = ous.get(0);
			if(openUser.getUser() == null ){
				User u = createUser(openUser.getNickname());
				ou.setUser(u);
			}else{
				ou.setUser(userDao.selectById(openUser.getUser().getId()));
			}
			/**
			 * 
			 */
			openUser.setNickname(ou.getNickname());
			openUser.setAccessToken(ou.getAccessToken());
			openUser.setUserInfo(ou.getUserInfo());
			openUserDao.update(openUser);
		}
		
		out.setSessionToken(loginLogic.execute(ou.getUser(), inDto.getRemoteAddress() , inDto.getCartId()));
		
		return out;
	}

	private User createUser(String nickname) {
		String username = getUsername(nickname);
		User u = new User();
		u.setUsername(username);
		u.setType(User.UserType.OPEN.getValue());
		u.setStatus(User.UserStatus.NORMAL.getValue());
		u.setRegisterTime(new Date());
		u.setLastLoginTime(new Date());
		userDao.insert(u);
		return u;
	}

	private String getUsername(String nickname) {
		boolean usernameExist = true;
		String username = nickname;
		int i = 0 ;
		while (usernameExist) {
			usernameExist = userDao.selectByUsername(username) != null;
			if(usernameExist){
				username =nickname + i;
				i++;
			}
		}
		return username;
	}

	
	
	
}
